home *** CD-ROM | disk | FTP | other *** search
/ SPACE 2 / SPACE - Library 2 - Volume 1.iso / program / 179 / gfa / gfagraph.doc < prev    next >
Encoding:
Text File  |  1987-09-16  |  60.1 KB  |  2,304 lines

  1. Figures and programs included in this Sample Chapter:
  2.  
  3. Figures:
  4.  
  5. Figure 3-1. Organization of Screen Memory for Monochrome Display.
  6. Figure 3-2 Organization of Color Screen Memory
  7. Figure 3-3. Cartesian Coordinate System
  8. Figure 3-4 Polar Coordinate System
  9. Figure 3-5. Raster Coordinate System
  10. Figure 3-6. Normalized Device Coordinate (NDC) System
  11. Figure 3-7. The Mandelbrot Primitive
  12. Figure 3-8. Mandelbrot Figure
  13. Figure 3-9. ANother Segment of the Mandelbrot Boundary.
  14.  
  15.  
  16.  
  17.  
  18.  
  19. Programs:
  20.  
  21. Program 3-1. LINEDRAW.PRG
  22. Program 3-2  STRING.BAS
  23. Program 3-3. KALEIDO.BAS
  24. Program 3-4. DRAGON.BAS
  25. Program 3-5. MANDELBROT.BAS
  26. Program 3-6. NEOWRITE.BAS
  27. Program 3-7. NEOLOAD.BAS
  28.  
  29.  
  30.  
  31. Chapter 3
  32.  
  33. ST Graphics
  34.  
  35. During the late 1950s and early 1960s, the Massachusetts Institute 
  36. of   Technoloy  (MIT) was the center of  the  computer  world,  an 
  37. academic   community  actively  involved  in  the   research   and 
  38. construction of supercomputer systems.
  39.      In 1963, Ivan Sutherland, a young graduate student working on 
  40. his doctoral dissertation at MIT,  could often be seen working far 
  41. into the night at the terminal of a giant mainframe computer.   He 
  42. wasn't  alone  in his labors.  Other students  doing  research  on 
  43. computers  had to use the late-night hours,  when  the  mainframes 
  44. weren't being used for other purposes, for exploring the limits of 
  45. this   fledgling  science  of  computers;   the  technology    for 
  46. microcomputers  had not even been developed.
  47.      Sutherland wrote and rewrote his lines of code.   After  much 
  48. revision, he was finally successful.  The monitor display cleared, 
  49. and a green line appeared:  The first computer graphic, a straight 
  50. line,  had  been  produced by the giant mainframe.   Not  much  by 
  51. today's  standards,  but this occasion marked the beginning  of  a 
  52. whole new art form --computer graphics.
  53.      This  single straight line evolved into the  Sketchpad  line-
  54. drawing  program.   Sutherland's early drawing program allowed the 
  55. user  to point at the screen with a light pen to  sketch  objects. 
  56. This  simple  system  was  the  predecessor  of  today's   complex 
  57. computer-assisted drawing (CAD) programs.
  58.      A   lot  had  to  happen  to   computers,   however,   before 
  59. sophisticated  computer  graphics could become a  reality.  For  a 
  60. while  computers  remained the expensive tools of  government  and 
  61. universities.  In  1965,  IBM introduced the  first  mass-produced 
  62. cathode ray tube (CRT),  but the price was more than $100,000  for 
  63. the  CRT only.   This price tag made entry into computer  graphics 
  64. practically  impossible for all but a few  specialized  users.  In 
  65. 1968,  Tektronics introduced the storage-tube CRT, which displayed 
  66. a drawing by retaining the image until the user replaced it.  This 
  67. type of display eliminated the need for costly memory and hardware 
  68. to store and display the image,  but the selling price of  $15,000 
  69. still placed the CRT far beyond the means of most users.
  70.     It  wasn't  until  the late 1970s and  early  1980s  that  the 
  71. microcomputer  industry exploded,  and computer wars  brought  the 
  72. price  and power of the personal computer within the reach of  the 
  73. middle-income person.
  74.      Soon,  powerful graphics programs such as DEGAS and NEOchrome 
  75. had  introduced many people to this new art form,  and  some  even 
  76. discovered  hidden talents.  And now that computer art has  become 
  77. accessible to so many people,  those people want to make the  best 
  78. possible use of its potential.
  79.      In this chapter,  we'll take you beyond DEGAS and  NEOchrome, 
  80. showing you how to develop and use the powerful graphics  routines 
  81. built into the ST.  Previously, exploitation of these features was 
  82. rather  difficult.  Most  programmers resorted to  C  or  assembly 
  83. language  programming when sophisticated graphics  were  required. 
  84. GFA  BASIC  delivers  the  power to  fully  utilize  the  graphics 
  85. potential of your ST.  Stunning graphics are easily obtained using 
  86. the GFA BASIC interpreter, while the GFA BASIC compiler allows you 
  87. to  develop  arcade-quality  games  in  BASIC,  then  execute  the 
  88. programs from the GEM Desktop with your program running at  speeds 
  89. rivaling those of assembly language.
  90.  
  91. Computer Graphics
  92.  
  93.      Computer graphics is a generic term which refers to any image 
  94. created with a computer.  This covers a wide range,  from a simple 
  95. line  on a monitor,  to intricate pictures developed with  drawing 
  96. programs,  and more.  Some computer scientists,  for instance, are 
  97. using  computers  to  control  lasers  which  produce  holographic 
  98. images.  Perhaps the scene from Star Wars where C3PO and Chew-baka 
  99. are  playing a chesslike game with holographic images  isn't  even 
  100. that far-fetched.
  101.      The  motion  picture industry,  in  recent  years,  has  used 
  102. computer graphics extensively.  The transformation of the  Genesis 
  103. planet in Star Trek II,  The Wrath of Khan, was an effect produced 
  104. with  fractal  graphics  --one of the most  fascinating  areas  of 
  105. computer  graphics  (and  one which we'll explore  later  in  this 
  106. chapter).   Disney  Studios  merged  real  action  with  computer-
  107. generated graphics in the movie TRON.  The Last Starfighter has 25 
  108. minutes of spectacular computer imagery, with each frame requiring 
  109. dozens of algorithms and hundreds of intricate designs.  In  fact, 
  110. such  movies  have  contributed to the birth  of  a  new  industry 
  111. devoted to enhancing computer-generated graphics technology,  with 
  112. one of the leaders in this new industry being Lucasfilm, a pioneer 
  113. in special effects since the Star Wars trilogy.
  114.      Although  holographic  imaging  and  Hollywood-type   special 
  115. effects  are  beyond the scope of this book,  it will show  you  a 
  116. fascinating world open to those who know the power of the ST.
  117.  
  118.  
  119. Graphics Capabilities
  120.  
  121. Good graphics require a minimum of a high-resolution display and a 
  122. large number of colors to work with.  Some rumors are beginning to 
  123. circulate  about computers for homes and businesses with  monitors 
  124. capable  of  displaying up to one million --1000  X   1000  --
  125. pixels.  Currently only dedicated graphics workstations,  such  as 
  126. the Sun or the Cray II, offer such capabilities, and both of these 
  127. are priced far beyond the home enthusiast's budget.   Although the 
  128. ST   doesn't  have  the  capabilities  of  a  dedicated   graphics 
  129. workstation, it is capable of displaying up to 256,000 pixels, for 
  130. a fraction of the cost.  Plus,  the palette of 512 colors makes it 
  131. ideal for producing colorful, exciting displays.
  132.     In  order to program graphics on the  ST,  it's  necessary  to 
  133. understand a little about the way the screen is displayed.  On the 
  134. monochrome screen,  each pixel (picture element) is represented by 
  135. a  single  bit of memory.   Each bit will be either a 0  or  a  1, 
  136. indicating whether each pixel is off or on,  respectively.  Screen 
  137. memory  is  organized  so that the first  byte  represents  the  8 
  138. pixels,  or  dots,  at  the top left corner of  the  screen.  Each 
  139. succeeding byte represents the next 8 pixels in  succession.  Each 
  140. ⇧screen  line consists of 640 pixels,  so the first 80  bytes  (80 
  141. times 8) represent the top row of the screen.  Since there are 400 
  142. lines of pixels vertically on the screen,  a total of 256,000 bits 
  143. are  used  to represent the monochrome  screen.  This  means  that 
  144. 32,000 bytes of screen memory are used to store the display.
  145.  
  146. Binary Decimal
  147.  00    0
  148.  01    1
  149.  10    2
  150.  11    3
  151.  
  152. Figure 3-1 Organization of Screen Memory for Monochrome Display.
  153.  
  154.     Color  screen  memory is organized in much  the  same  way  as 
  155. monochrome screen memory,  but instead of single bits representing 
  156. single pixels, groups of bits are used to represent each pixel. In 
  157. medium resolution, a pixel may be one of four colors. Two bits are 
  158. used to create the four possible colors:
  159.     The  first  byte of screen memory represents  the  first  four 
  160. pixels at the upper left corner of the screen.  The two high-order 
  161. bits  specify  the color in the first pixel,  the  next  two  bits 
  162. represent the color in the second pixel,  and so on. There are 640 
  163. pixels per row; each row requires 160 bytes of memory. Since there 
  164. are only 200 vertical rows of pixels,  only 32,000 bytes of memory 
  165. are necessary to store a screen.
  166.     In low resolution,  a pixel can be one of 16 colors,  so  four 
  167. bits are required to represent a single pixel.
  168.  
  169. 0000 = 0        1000 = 8
  170. 0001 = 1        1001 = 9
  171. 0010 = 2        1010 = 10
  172. 0011 = 3        1011 = 11
  173. 0100 = 4        1100 = 12
  174. 0101 = 5        1101 = 13
  175. 0110 = 6        1110 = 14
  176. 0111 = 7        1111 = 15
  177.  
  178.     Each  byte describes the color of only 2  pixels.  But  again, 
  179. since there are only 320 pixels per line,  and 200 vertical lines, 
  180. only 32,000 bytes are required to represent a full screen.
  181.  
  182. Figure 3-2 Organization of Color Screen Memory
  183.  
  184.     As mentioned previously,  the ST is capable of displaying  512 
  185. colors,  but  only 16 colors may be displayed at one time (in  low 
  186. resolution).  Each  value stored in color memory corresponds to  a 
  187. hardware color register.
  188.      In GFA BASIC,  the command COLOR defines the color to be used 
  189. by  a  graphics command.  If you do not specify a color  before  a 
  190. graphics command,  either the default color or the color last used 
  191. is selected.  Usually,  the default color is color 1,  which has a 
  192. default value of black, 0.
  193.  
  194. Graphics Programming Techniques
  195.  
  196. Entire  books  have  been  written about  the  various  phases  of 
  197. computer  graphics.  Each section of this chapter could  be  dealt 
  198. with  in much greater detail.  Instead,  we're going to  introduce 
  199. you,  quickly and painlessly, to graphics techniques, point you in 
  200. the  right  direction,  and then leave you to  the  excitement  of 
  201. discovery  as you explore this world with your staunch  ally,  GFA 
  202. BASIC.
  203.    As with any voyage,  some preliminary attention to detail  must 
  204. be undertaken.  After all,  to use the graphics commands, you must 
  205. at  least be able to tell the computer where you want  the  object 
  206. you're drawing to appear.
  207.      There are several coordinate systems in use, but the two most 
  208. common   are  the  Cartesian  coordinate  system  and  the   polar 
  209. coordinate system.
  210.      In the Cartesian coordinate system, the two-dimensional plane 
  211. is assigned two axes:  the horizontal axis, usually labeled x, and 
  212. the vertical axis, Çusually labeled y. By convention, the positive 
  213. direction  of  the  x-axis  is to  the  right,  but  the  positive 
  214. direction of the y-axis can be either up or down, depending on the 
  215. application. In geometry and most other mathematical applications, 
  216. the positive direction of the y-axis is up,  but on most  computer 
  217. systems,  the positive direction is down.  Points in the plane are 
  218. represented by ordered pairs (x,y), where x is the distance of the 
  219. point from the y-axis and y is the distance of the point from  the 
  220. x-axis.  The  point (0,0) is called the origin because it  is  the 
  221. point where the x and y axes intersect,  the point from which  all 
  222. other points in the plane are located.
  223.    The  location of the origin is another disputed aspect  of  the 
  224. Cartesian   coordinate  system.   In  geometry,   the  origin   is 
  225. traditionally located in the lower left corner of the display with 
  226. the  positive x and y axes extending toward the right and  top  of 
  227. the display,  respectively. However, on most computers, the origin 
  228. is located in the upper left corner of the screen,  because of the 
  229. way the monitor draws the display.  Another possible location  for 
  230. the origin is the center of the display. This orientation makes it 
  231. easy  to  graph  both  negative as  well  as  positive  values  -- 
  232. something the other two systems ignore.  Either of these locations 
  233. is equally valid, and conversion from one orientation to the other 
  234. is simple, so the choice of which system to use is usually left up 
  235. to the user.
  236.  
  237.  
  238. Figure 3-3. Cartesian Coordinate System
  239.  
  240.  
  241.  
  242. Figure 3-4 Polar Coordinate System
  243.  
  244.  
  245.     The Cartesian coordinate system cooresponds closely  with  the 
  246. real  world,  which makes it ideal for most applications,  but  in 
  247. situations where rotation is necessary,  the Cartesian  coordinate 
  248. system is difficult to use.     Two systems of referencing are  in 
  249. common use with computers:  the normalized device coordinate (NDC) 
  250. system, and the raster coordinate (RC) system
  251.  
  252. . The NDC system addresses the graphics display independent of the 
  253. device's display size, while the RC system addresses the device in 
  254. actual  display units.  The RC system is the system used  on  most 
  255. microcomputers.  With this system, the screen is divided into rows 
  256. and columns of dots,  or pixels.  The pixels in the top row have a 
  257. vertical, or y, coordinate of 0. The y coordinate increases as you 
  258. move toward the bottom of the screen. The bottom row of the screen 
  259. has  a  y coordinate value of 199 on a color system and 399  on  a 
  260. monochrome system. The leftmost column of pixels has a horizontal, 
  261. or x, coordinate of 0.
  262.  
  263.      The x coordinate increases as you move toward the right  edge 
  264. of the display,  where each pixel in the rightmost column has  the 
  265. value of 319 on color systems in low resolution and 639 in  medium 
  266. or high resolution.
  267.                                                             
  268. Figure 3-5. Raster Coordinate System
  269.  
  270.  
  271.      The ST also supports the NDC system.  It's difficult to write 
  272. a  single  program  that will work with  the  different  types  of 
  273. devices,  because  almost  every  graphics  output  device  has  a 
  274. different maximum horizontal and vertical resolution. That's where 
  275. the NDC system becomes expedient.
  276.    The NDC system offers the programmer a means by which  graphics 
  277. drawn  on one computer screen or printer will look the  same  when 
  278. drawn   on  other  computer  screens  or  printers  of   different 
  279. resolutions.  With the NDC system,  all graphics output is sent to 
  280. an  imaginary device that is 32,768 pixels wide and 32,768  pixels 
  281. high. These pixels are grouped differently from those under the RC 
  282. system.  The y axis begins with 0 at the bottom of the screen, and 
  283. moves up to the top row of pixels numbering 32,767.  As in the  RC 
  284. system,  the x axis is numbered from left to right.  The  leftmost 
  285. column of pixels is 0, and the rightmost column is 32,767.
  286.     Two  coordinate-referencing systems on one computer  may  seem 
  287. difficult to grasp, but usually you'll only be dealing with the RC 
  288. system in GFA BASIC.  You should be aware of the NDC system, as it 
  289. does have value with GDOS and some VDI functions.
  290.  
  291. Figure 3-6. Normalized Device Coordinate (NDC) System
  292.  
  293.  
  294. Resolving a problem
  295.  
  296.      The  ST may be configured in low resolution (320x200  pixels) 
  297. and medium resolution (640x200 pixels) with a color monitor, or in 
  298. high resolution (640x400 pixels) with a monochrome  monitor.  It's 
  299. very easy to include a simple check for the resolution mode,  then 
  300. use  program  modules  applicable for  th  resolution.  It's  even 
  301. possible to affect a change of resolution from GFA BASIC by  using 
  302. an XBIOS function.  At the very least,  you should include a check 
  303. in your program to determine which mode of resolution the computer 
  304. is  displaying.  If necessary,  you can then display an Alert  box 
  305. informing   the  user  that  the  program  requires  a   different 
  306. resolution.  Good programming practice dictates that your  program 
  307. be compatible with different systems, if possible. Especially with 
  308. programs  that use graphics,  the effect you've labored to  create 
  309. will be lost if the proper mode of resolution isn't selected.
  310.     XBIOS is a group of extended input/output functions which  are 
  311. available  to  the programmer.  For more information  about  XBIOS 
  312. routines,  refer  to Appendix F.  GFA BASIC makes these  functions 
  313. available  to  you  by using the same bindings as  those  used  by 
  314. programmers  working in C.  Refer to Appendix F for a list of  the 
  315. XBIOS functions and bindings.
  316.    To check the resolution of a system,  XBIOS 4, called getrez in 
  317. most literature about the ST,  can be used.
  318.  
  319. PROCEDURE check_rez
  320.  '
  321.  rez=XBIOS(4)
  322.  '
  323. RETURN
  324.  
  325.    This  procedure  will  return  the  screen  resolution  in  the 
  326. variable, rez:
  327.  
  328. 0 = low resolution (320x200, 16 colors)
  329. 1 = medium resolution (640x200, 4 colors)
  330. 2 = high resolution (640x400, monochrome)
  331.  
  332.    To change resolution modes, use the following procedure. Define 
  333. rez  equal  to  the  value of the  desired  resolution  then  call 
  334. set_rez.   (Note:   high  resolution  is  only  available  with  a 
  335. monochrome monitor.)
  336.  
  337. PROCEDURE set_rez
  338.  '
  339.   dummy=XBIOS(5,L:-1,L:-1,W:rez)
  340.  '
  341. RETURN
  342.  
  343.    Switching from medium to low resolution will present no special 
  344. problems.  However, when you force a switch from low resolution to 
  345. medium resolution,  graphics commands will not appear on the right 
  346. side of the screen. The operating system still assumes that values 
  347. greater than 319 for X are off the screen.  Meanwhile all graphics 
  348. with X coordinates less than 320,  will be shown, on the left side 
  349. of  the  screen.  Using the PRINT command to display  text  should 
  350. present no problem.
  351.  
  352. GFA BASIC Graphics Commands
  353.  
  354.     As the following list of graphics  commands  illustrates,  GFA 
  355. BASIC provides a powerful and easy to use programming enviornment. 
  356. More information about these commands can be found in Chapter Two, 
  357. GFA BASIC Commands and Functions or in Appendix A, Quick Reference 
  358. GFA BASIC Glossary.
  359.  
  360.  
  361. BITBLT
  362. BOX
  363. CIRCLE
  364. CLEARW
  365. CLOSEW
  366. CLS
  367. COLOR
  368. DEFFILL
  369. DEFLINE
  370. DEFMARK
  371. DEFMOUSE
  372. DRAW
  373. ELLIPSE
  374. FILL
  375. FULLW
  376. GET
  377. GRAPHMODE
  378. HARDCOPY
  379. HIDEM
  380. INFOW
  381. LINE
  382. MOUSE
  383. MOUSEX
  384. MOUSEY
  385. MOUSEK
  386. OPENW
  387. PBOX
  388. PCIRCLE
  389. PELLIPSE
  390. PRBOX
  391. PLOT
  392. POINT
  393. POLYLINE
  394. POLYFILL
  395. POLYMARK
  396. PUT
  397. RBOX
  398. SETCOLOR
  399. SGET
  400. SHOWM
  401. SPRITE
  402. SPUT
  403. TEXT
  404. TITLEW
  405. VSYNC
  406.  
  407.  
  408. Graphics on a 2-dimensional surface
  409.  
  410.    The simplest of the graphic commands in GFA BASIC are the  line 
  411. drawing  commands.  The  simplest of these is  the  LINE  command. 
  412. Remember,  the coordinates used by the LINE command and the  other 
  413. GFA  BASIC  graphics commands are in the  Raster  Coordinate  (RC) 
  414. System.
  415.  
  416. Figure  3-7.  Simple  graphic produced by Program  3-1  using  GFA 
  417. BASIC.
  418.  
  419.    The following short program demonstrates the ease with which  a 
  420. simple  graphic  screen can be developed using the  LINE  and  BOX 
  421. commands.
  422.     GFA BASIC listings for this book have been produced  by  first 
  423. selecting  the dir item on the Editor's menu bar,  then  entering, 
  424. DEFLIST 0,  which causes all commands and function to be displayed 
  425. (and  printed LLIST) in all capitol letters.  Variable  names  and 
  426. names  of procedures will be in lower case  letters.  
  427.  
  428. Program  3-1 
  429. LINEDRAW.PRG
  430.  
  431.  
  432. ' Simple Line Drawing Demo
  433. '
  434. LINE 0,100,150,100
  435. LINE 500,100,640,100
  436. BOX 150,50,500,150
  437. LINE 325,25,150,50
  438. LINE 325,25,500,50
  439. BOX 295,80,355,150
  440. BOX 175,90,255,130
  441. LINE 215,90,215,130
  442. LINE 175,110,255,110
  443. BOX 390,90,470,130
  444. LINE 430,90,430,130
  445. LINE 390,110,470,110
  446. '
  447.  
  448.  
  449.     In order to make the screen a little more  interesting,  we'll 
  450. use DEFFILL to select a pattern style and colors to be used by the 
  451. FILL command. For more information about DEFFILL, or any other GFA 
  452. BASIC command, refer to Chapter Two. 
  453.  
  454. DEFFILL 3
  455. '
  456. FILL 5,195
  457. '
  458. DEFFILL 1,3
  459. FILL 330,30
  460. '
  461. DEFFILL 1,2
  462. FILL 5,5
  463. '
  464. DEFFILL 2,2
  465. FILL 155,55
  466. '
  467. DEFFILL 2,1
  468. FILL 310,115
  469.  
  470.  
  471.     The  image  produced  will only  flash  on  the  screen,  then 
  472. disappear as the edit screen reappears when the program ends .  We 
  473. need to place GFA BASIC into a loop which repeats until we  decide 
  474. it's time to exit the loop (and the program) and send a signal  to 
  475. the  interpretter.  All  that is needed is a  REPEAT...UNTIL  loop 
  476. which will wait for any key to be pressed.  When a key is pressed, 
  477. the program ends.
  478.  
  479.  
  480. '
  481. REPEAT
  482. UNTIL INKEY$<>""
  483. END
  484.  
  485.  
  486.    Generally,  we'll be discussing each routine used in a program, 
  487. rather  than  the individual commands used to obtain  the  desired 
  488. result. If a more detailed explanation of a command or function is 
  489. needed, refer to Chapter 2 or Appendix A.
  490.  
  491.  
  492. String Art
  493.  
  494. Only  a short step from line drawing is an interesting  art  form, 
  495. String  Art.  String  Art  may be either a  succession  of  points 
  496. connected by lines,  or a  sequence of lines drawn on the  screen. 
  497. Computer  generated  String Art may even take the  form  of  lines 
  498. dancing  around the screen,  as in this program.  STRING.BAS  will 
  499. draw each screen and then wait for the user to press a key  before 
  500. continuing.  The  last  screen  prompts the user  for  a  positive 
  501. number. This number determines how many petals to draw on a rose.
  502.     Originally we intended this part to work only  with  integers, 
  503. but  we discovered that some very interesting patterns develop  if 
  504. you enter compound numbers (numbers with a fractional  part).  Try 
  505. several  different values.  STRING.BAS will display the  rose  for 
  506. each and then wait for you to press a key.  If you'd like to  stop 
  507. the drawing process to any time, press a key. When the drawing has 
  508. stopped,  pressing a key will prompt you for a new number. Enter 0 
  509. to exit STRING.BAS.  The LINE command is used to draw each of  the 
  510. screens.
  511.  
  512. Program 3-2. String Art
  513.  
  514.     The  first thing String Art does is check the  current  screen 
  515. resolution  and set the global variables x_size and y_size to  the 
  516. width and height of the screen, respectively.
  517.  
  518.  
  519. ' What resolution is the ST in?
  520. '   xbios(4) returns 0 if low ,  1 if medium,  and 2  if  high 
  521. resolution
  522. rez=XBIOS(4)
  523. '
  524. ' set x_size to the width and y_size to the height of the screen
  525. '
  526. IF rez=0
  527.  x_size=320
  528.  y_size=200
  529. ENDIF
  530. IF rez=1
  531.  x_size=640
  532.  y_size=200
  533. ENDIF
  534. IF rez=2
  535.  x_size=640
  536.  y_size=400
  537. ENDIF
  538. '
  539.  
  540.  
  541.     STRING.BAS  is  written  so that each screen  is  drawn  by  a 
  542. separate  procedure;  this  makes it easy to delete  some  of  the 
  543. existing screens or add new ones of your own. After each screen is 
  544. drawn, STRING.BAS waits for any key to be pressed before it clears 
  545. the screen and draws the next screen.
  546.  
  547. GOSUB screen_1
  548. GOSUB wait_key
  549. CLS
  550. GOSUB screen_4
  551. GOSUB wait_key
  552. CLS
  553. GOSUB screen_2
  554. GOSUB wait_key
  555. CLS
  556. GOSUB screen_3
  557. GOSUB wait_key
  558. CLS
  559. GOSUB screen_5
  560. '
  561. END
  562.  
  563.  
  564.     The  rest  of STRING.BAS consists of the  procedures  used  in 
  565. calculating or actually drawing the figures.
  566.  
  567.  
  568. '
  569. '
  570. ' PROCEDURE wait_key
  571. '
  572. '    This subroutine pauses the program until the user  presses  a 
  573. key.
  574. '
  575. PROCEDURE wait_key
  576.  REPEAT
  577.  UNTIL inkey$<>""
  578. RETURN              ! end of wait_key
  579.  
  580.  
  581.    The following procedure converts the radius and theta values of 
  582. polar  coordinates to Cartesian coordinates.  See the  section  on 
  583. coordinate systems earlier in this chapter for details.
  584.  
  585.  
  586. '
  587. '
  588. ' PROCEDURE polar_to_rect
  589. '
  590. '   This procedure converts from the polar coordinate system to the
  591. ' rectangular coordinate system. Pass r (radius) and theta to
  592. '  polar_to_rect  and  it will return the x and y  values  in  the GLOBAL
  593. ' VARIABLES x and y.
  594. '
  595. PROCEDURE polar_to_rect(r,theta)
  596.  x=r*COS(theta)
  597.  y=r*SIN(theta)
  598. RETURN              ! end of polar_to_rect
  599.  
  600.  
  601.    This routine is used to draw two of the screens in  STRING.BAS, 
  602. by calculating the values necessary for the end points of the line 
  603. to  trace a limacon.  Procedure limacon is used in the  procedures 
  604. screen --1 and screen --2.  The first parameter of limacon is  the 
  605. angle theta for which the radius is to be calculated. The next two 
  606. parameters  are constants which modify the shape of  the  limacon. 
  607. You might find it interesting to play around with these constants.
  608.  
  609.  
  610. '
  611. '
  612. ' PROCEDURE limacon
  613. '
  614. '   This procedure returns the value of r (radius) necessary to draw
  615. '  a limacon given the angle of theta and two scaling  factors,  m and n.
  616. ' NOTE: r is a GLOBAL VARIABLE.
  617. '
  618. PROCEDURE limacon(theta,m,n)
  619.  r=m+n*COS(theta)
  620. RETURN             ! end of limacon
  621.  
  622.  
  623.    Procedure rose generates one of the prettiest patterns possible 
  624. using polar coordinates. Its output is used in screen 5.
  625.  
  626.  
  627. '
  628. '
  629. ' PROCEDURE rose
  630. '
  631. '   This procedure returns the value of r (radius) necessary to 
  632. draw
  633. ' a rose given the angle theta,  the number of leaves,  n,  and  a 
  634. scaling
  635. ' factor m. n determines the number of leaves in the rose. If n is 
  636. even,
  637. ' then the rose will have 2n petals;  if n is odd, there will be n 
  638. leaves.
  639. ' NOTE: r is a GLOBAL VARIABLE.
  640. '
  641. PROCEDURE rose(theta,n,m)
  642.  r=m*COS(n*theta)
  643. RETURN             
  644.  
  645.   end of rose denominator is used in screen --5 to  determine  how 
  646. much  of  the flower to draw.  The denominator  returned  by  this 
  647. procedure  is  used to calculate the upper limit of  the  function 
  648. before it is plotted.
  649.  
  650.  
  651. '
  652. '
  653. ' PROCEDURE denominator
  654. '
  655. '   This  routine returns the denominator of a number  with  a 
  656. fractional component.  
  657. '
  658. PROCEDURE denominator(num)
  659.  LOCAL k
  660.  LOCAL a
  661.  LOCAL b
  662.  '
  663.  k=1
  664.  found=0
  665.  a=num
  666.  GOSUB denom(a)
  667.  IF found=0
  668.   a=num/SQR(2)
  669.   GOSUB denom(a)
  670.  ENDIF
  671.  IF found=0
  672.   a=num/SQR(3)
  673.   GOSUB denom(a)
  674.  ENDIF
  675.  IF found=0
  676.   a=num/SQR(5)
  677.   GOSUB denom(a)
  678.  ENDIF
  679.  IF found=0
  680.   a=num/PI
  681.   GOSUB denom(a)
  682.  ENDIF
  683.  IF found=0
  684.   a=num/PI^2
  685.   GOSUB denom(a)
  686.  ENDIF
  687.  IF found=0
  688.   a=num/EXP(1)
  689.   GOSUB denom(a)
  690.  ENDIF
  691.  IF found=0
  692.   a=num*PI
  693.   k=PI
  694.   GOSUB denom(a)
  695.  ENDIF
  696.  IF found=0
  697.   a=num*PI^2
  698.   k=PI^2
  699.   GOSUB denom(a)
  700.  ENDIF
  701.  IF found=0
  702.   k=1
  703.  ENDIF
  704.  '
  705.  d=b*k
  706. RETURN
  707. '
  708. '
  709. ' PROCEDURE denom
  710. '
  711. '   This routine actually calculates the denominator of the fraction.
  712. '
  713. PROCEDURE denom(a)
  714.  LOCAL c
  715.  LOCAL dun
  716.  c=ABS(a)
  717.  b=1
  718.  REPEAT
  719.   dun=0
  720.   b=b/c
  721.   c=(1/c)-INT(1/c)
  722.   IF b>100000
  723.    dun=1
  724.   ENDIF
  725.  UNTIL c<1.0E-06 OR dun<>0
  726.  IF dun<>1
  727.   b=INT(b)
  728.   found=1
  729.  ENDIF
  730. RETURN
  731.  
  732.  
  733.    The remaining five procedures actually draw the  screens.  Each 
  734. of them is well documanted in the code so we won't go into  detail 
  735. on them.
  736.  
  737.  
  738. '
  739. '
  740. ' PROCEDURE screen_1
  741. '
  742. '   This procedure draws the first screen using the procedures,
  743. ' NOTE: the following variables are GLOBAL: rez, x_size, and y_size.
  744. '
  745. PROCEDURE screen_1
  746.  LOCAL steps
  747.  LOCAL y_scale    !y scaling factor
  748.  LOCAL x_scale    !x scaling factor
  749.  LOCAL l_limit    !lower limit of funtion
  750.  LOCAL u_limit    !upper limit of function
  751.  LOCAL x_inc     !x or theta increment
  752.  IF rez=0
  753.   steps=1000*PI
  754.  ENDIF
  755.  IF rez=1
  756.   steps=2000*PI
  757.  ENDIF
  758.  IF rez=2
  759.   steps=4000*PI
  760.  ENDIF
  761.  '
  762.  y_scale=y_size/2
  763.  l_limit=0
  764.  u_limit=2*PI
  765.  x_scale=x_size/2
  766.  x_inc=x_scale/steps
  767.  '
  768.  FOR theta=l_limit TO u_limit STEP x_inc
  769.   GOSUB limacon(theta,y_scale*3/4,y_scale*3/4)
  770.   GOSUB polar_to_rect(r,theta)
  771.   x1=x
  772.   y1=y
  773.   GOSUB limacon(theta,y_scale*3/4,-y_scale*3/4)
  774.   GOSUB polar_to_rect(r,theta)
  775.   x2=x
  776.   y2=y
  777.   IF rez<>1
  778.    LINE x1+x_scale,y1+y_scale,x2+x_scale,y2+y_scale
  779.   ELSE
  780.    LINE x1*2+x_scale,y1+y_scale,x2*2+x_scale,y2+y_scale
  781.   ENDIF
  782.  NEXT theta
  783. RETURN             ! end of screen_1
  784. '
  785. '
  786. ' PROCEDURE screen_2
  787. '
  788. '   This procedure draws the second screen using the procedures,
  789. ' NOTE: the following variables are GLOBAL: rez, x_size, and y_size.
  790. '
  791. PROCEDURE screen_2
  792.  LOCAL steps
  793.  LOCAL y_scale    !y scaling factor
  794.  LOCAL x_scale    !x scaling factor
  795.  LOCAL l_limit    !lower limit of funtion
  796.  LOCAL u_limit    !upper limit of function
  797.  LOCAL x_inc     !x or theta increment
  798.  IF rez=0
  799.   steps=250*PI
  800.  ENDIF
  801.  IF rez=1
  802.   steps=500*PI
  803.  ENDIF
  804.  IF rez=2
  805.   steps=1000*PI
  806.  ENDIF
  807.  '
  808.  y_scale=y_size/2
  809.  l_limit=0
  810.  u_limit=2*PI
  811.  x_scale=x_size/(u_limit-l_limit)
  812.  x_inc=x_scale/steps
  813.  ' ferp
  814.  FOR theta=l_limit TO u_limit STEP x_inc
  815.   GOSUB limacon(theta,y_scale*9/14,y_scale)
  816.   GOSUB polar_to_rect(r,theta)
  817.   x1=x
  818.   y1=y
  819.   GOSUB limacon(theta,y_scale*9/14,-y_scale)
  820.   GOSUB polar_to_rect(r,theta)
  821.   x2=x
  822.   y2=y
  823.   IF rez<>1
  824.    LINE x2+x_size*15/16,y2+y_size/2,x1+x_size/16,y1+y_size/2
  825.   ELSE
  826.    LINE x2*2+x_size*15/16,y2+y_size/2,x1*2+x_size/16,y1+y_size/2
  827.   ENDIF
  828.  NEXT theta
  829. RETURN             ! end of screen_2
  830. '
  831. '
  832. ' PROCEDURE screen_3
  833. '
  834. '   This procedure draws the third screen using the procedures,
  835. ' NOTE: the following variables are GLOBAL: rez, x_size, and y_size.
  836. '
  837. PROCEDURE screen_3
  838.  LOCAL steps
  839.  LOCAL y_scale    !y scaling factor
  840.  LOCAL x_scale    !x scaling factor
  841.  LOCAL l_limit    !lower limit of funtion
  842.  LOCAL u_limit    !upper limit of function
  843.  LOCAL x_inc     !x or theta increment
  844.  IF rez=0
  845.   steps=500*PI
  846.  ENDIF
  847.  IF rez=1
  848.   steps=750*PI
  849.  ENDIF
  850.  IF rez=2
  851.   steps=1000*PI
  852.  ENDIF
  853.  '
  854.  y_scale=y_size/2
  855.  l_limit=0
  856.  u_limit=8*PI
  857.  x_scale=x_size/2
  858.  x_inc=x_scale/steps
  859.  '
  860.  FOR i=l_limit TO u_limit STEP x_inc
  861.   x1=SIN(i)+1
  862.   x2=SIN(i-3*PI/4)+1
  863.   y1=COS(i*3/4)+1
  864.   y2=COS((i-3*PI/4)*3/4)+1
  865.   LINE x1*x_scale,y1*y_scale,x2*x_scale,y2*y_scale
  866.   PAUSE 1
  867.  NEXT i
  868. RETURN             ! end of screen_3
  869. '
  870. '
  871. ' PROCEDURE screen_4
  872. '
  873. '   This procedure draws the fourth screen using the procedures,
  874. ' NOTE: the following variables are GLOBAL: rez, x_size, and y_size.
  875. '
  876. PROCEDURE screen_4
  877.  LOCAL steps
  878.  LOCAL y_scale    !y scaling factor
  879.  LOCAL x_scale    !x scaling factor
  880.  LOCAL l_limit    !lower limit of funtion
  881.  LOCAL u_limit    !upper limit of function
  882.  LOCAL x_inc     !x or theta increment
  883.  IF rez=0
  884.   steps=250*PI
  885.  ENDIF
  886.  IF rez=1
  887.   steps=500*PI
  888.  ENDIF
  889.  IF rez=2
  890.   steps=1000*PI
  891.  ENDIF
  892.  '
  893.  y_scale=y_size/2
  894.  l_limit=0
  895.  u_limit=5*PI
  896.  x_scale=x_size/2
  897.  x_inc=x_scale/steps
  898.  '
  899.  FOR i=l_limit TO u_limit STEP x_inc
  900.   x1=SIN(i)+1
  901.   x2=SIN(i-3*PI/4)+1
  902.   y1=COS(i*5/6)+1
  903.   y2=COS((i-3*PI/4)*5/6)+1
  904.   LINE x1*x_scale,y1*y_scale,x2*x_scale,y2*y_scale
  905.   PAUSE 1
  906.  NEXT i
  907. RETURN             ! end of screen_4
  908. '
  909. '
  910. ' PROCEDURE screen_5
  911. '
  912. '   This procedure draws the fifth screen using the procedures,
  913. ' NOTE: the following variables are GLOBAL: rez, x_size, and y_size.
  914. '
  915. PROCEDURE screen_5
  916.  LOCAL steps
  917.  LOCAL y_scale    !y scaling factor
  918.  LOCAL x_scale    !x scaling factor
  919.  LOCAL l_limit    !lower limit of funtion
  920.  LOCAL u_limit    !upper limit of function
  921.  LOCAL x_inc     !x or theta increment
  922.  IF rez=0
  923.   steps=500*PI
  924.  ENDIF
  925.  IF rez=1
  926.   steps=1000*PI
  927.  ENDIF
  928.  IF rez=2
  929.   steps=4000*PI
  930.  ENDIF
  931.  '
  932.  y_scale=y_size/2
  933.  l_limit=0
  934.  x_scale=x_size/2
  935.  '
  936.  PRINT "  This routine draws flowers with the"
  937.  PRINT "number of petals that you specify."
  938.  PRINT "If you enter an odd number, n, a flower"
  939.  PRINT "with n petals will be drawn. If you"
  940.  PRINT "enter an even number, n, a flower with"
  941.  PRINT "2n petals will be drawn. Flowers with"
  942.  PRINT "large numbers of petals look like"
  943.  PRINT "filled-in circles, so keep your number"
  944.  PRINT "small. You can stop the drawing at any"
  945.  PRINT "by pressing a key. When the drawing has"
  946.  PRINT "stopped, press any key to continue."
  947.  PRINT
  948.  REPEAT
  949.   INPUT "Input a positive number (0 to quit) ";n
  950.  UNTIL n>=0
  951.  WHILE n>0
  952.   CLS
  953.   u_limit=1
  954.   d=1
  955.   IF INT(n)<>n
  956.    found=0
  957.    GOSUB denominator(n)
  958.    u_limit=d
  959.   ENDIF
  960.   IF ODD(n*d) AND ODD(d)
  961.    u_limit=PI*u_limit
  962.   ELSE
  963.    u_limit=2*PI*u_limit
  964.   ENDIF
  965.   steps=2000*PI*n
  966.   x_inc=x_scale/steps
  967.   theta=l_limit
  968.   a$=""
  969.   WHILE theta<=u_limit AND a$=""
  970.    GOSUB rose(theta,n,y_scale)      ! rose returns r
  971.    GOSUB polar_to_rect(r,theta)     ! polar returns x and y
  972.    x1=x
  973.    y1=y
  974.    GOSUB rose(theta-PI/(3*n),n,y_scale)
  975.    GOSUB polar_to_rect(r,theta-PI/(3*n))
  976.    IF rez=1
  977.     LINE x1*2+x_scale,y1+y_scale,x*2+x_scale,y+y_scale
  978.    ELSE
  979.     LINE x1+x_scale,y1+y_scale,x+x_scale,y+y_scale
  980.    ENDIF
  981.    theta=theta+x_inc
  982.    a$=INKEY$
  983.   WEND
  984.   GOSUB wait_key
  985.   PRINT "Previous Number = ";n;" (";n*d;"/";d;")"
  986.   REPEAT
  987.    INPUT "Input a positive integer (0 to quit) ";n
  988.   UNTIL n>=0
  989.  WEND
  990. RETURN             ! end of screen_5
  991.  
  992.  
  993. Kaleidoscope
  994.  
  995.    Here's a colorful demonstration program reminiscent of the Lava 
  996. Lamps popular during the 1960s. You may have seen a version of ths 
  997. program  running  on the Commodore Amiga,  or even  a  C  language 
  998. version  on  th  ST.  KALEDIOSCOPE.BAS runs  from  the  GFA  BASIC 
  999. interpretter.  This program also demonstrates the use of some  new 
  1000. graphic  commands.  Note  that "!" separates a  comment  from  the 
  1001. command on the same line.  Also, the ' mark is used in lines which 
  1002. contain only a comment.   In this program you'll see color spelled 
  1003. two  ways;  color and colour.  Color is a GFA BASIC command  which 
  1004. sets the color to be used by a graphics command,  and the  in-line 
  1005. Syntax  checker  will  interpret  it  as  such.  Often  to  use  a 
  1006. descriptive   label  or  variable  name,   it's  advantageous   to 
  1007. deliberately mis-spell a word.  Be sure to keep track of such mis-
  1008. spellings, and mis-spell the word the same way every time.
  1009.  
  1010. Program 3-3. KALEDIO.BAS
  1011.  
  1012.     Begin  by reserving an area of memory to  hold  the  alternate 
  1013. palette colors.   
  1014.  
  1015. DIM palette(15),pal(15),pal2(15)
  1016. '
  1017. shape=0          ! Initial shape is a circle.
  1018. HIDEM           ! Hide mouse
  1019. '
  1020. '
  1021. ' Check for low resolution
  1022. '
  1023. IF XBIOS(4)<>0
  1024.  alrt$="KALEIDOSCOPE only works in|Low Res (320X200 Pixels)"
  1025.  ALERT 3,alrt$,1,"Oops!!",b
  1026.  END
  1027. ENDIF
  1028.  
  1029.  
  1030.     Next,  set  up  an alternate  color  palette.  Each  color  is 
  1031. represented by three hexadecimal numbers,  representing the  three 
  1032. color guns of an RGB (Red,  Green, and Blue) monitor, ranging from 
  1033. 0  for a gun which is turned off,  to 7 for a gun at  the  highest 
  1034. output level. You can experiment with the numbers on the following 
  1035. table to observe the effects of different numbers on the  display. 
  1036. (For more inforamtion about colors and the SETCOLOR command, refer 
  1037. to Chapter 2.)
  1038.     You  can use the Control Panel desk accessory to  get  instant 
  1039. feedback  on mixing colors.  When you use it to mix  colors  using 
  1040. different levels of red, green, and blue, the panel displays these 
  1041. color levels as numbers from 0 to 7.  The desktop, and the COntrol 
  1042. Panel, will change colors as you change the settings. It's best to 
  1043. write down the numbers displayed as you proceed,  as it may become 
  1044. necessary  to  turn off your ST and reboot in order to  restore  a 
  1045. readable  screen.  Use these numbers as the hexadecimal values  in 
  1046. the  following table to install the colors in your color  palette, 
  1047. as demonstrated below.
  1048.  
  1049.  
  1050. '
  1051. '
  1052. ' Set up color table
  1053. '
  1054. pal2(0)=&H555
  1055. pal2(1)=&H700
  1056. pal2(2)=&H60
  1057. pal2(3)=&H7
  1058. pal2(4)=&H5
  1059. pal2(5)=&H520
  1060. pal2(6)=&H50
  1061. pal2(7)=&H505
  1062. pal2(8)=&H222
  1063. pal2(9)=&H77
  1064. pal2(10)=&H55
  1065. pal2(11)=&H707
  1066. pal2(12)=&H505
  1067. pal2(13)=&H550
  1068. pal2(14)=&H770
  1069. pal2(15)=&H555
  1070. '
  1071.  
  1072.  
  1073.    Now we'll display an Alert box containing the program title and 
  1074. a few pieces of necessary preliminary  information.  Usually,  you 
  1075. won't  want to use an Alert box for displaying anything  except  a 
  1076. warning,  but  in this case very little information  is  required. 
  1077. Notice  that  as you type in the text for the variable  alrt$  the 
  1078. screen will scroll to the left.  When you move to the next line, a 
  1079. dollar  sign is displayed at the point where the text exceeds  the 
  1080. 80  character screen limit.  This dollar sign signifies that  more 
  1081. text exists on this line
  1082.  
  1083. .
  1084.  
  1085.  
  1086. '
  1087. ' Display title box
  1088. '
  1089. alrt$="    Kaleidoscope|Left Button  Restarts|Right  Button 
  1090. Changes Shape|Both Buttons End Program|"
  1091. ALERT 1,alrt$,1,"Okay",b
  1092. '
  1093.  
  1094.  
  1095.    Since we plan to tamper with the color scheme, it would only be 
  1096. polite  to  provide a means to reset the colors when  we  end  our 
  1097. program.
  1098.  
  1099.  
  1100. GOSUB save_palette    '
  1101. ' Setcolor 0,5,5,5     ! Set background to gray.
  1102. '
  1103. GOSUB set_colour      ! Install new palette
  1104. '
  1105. start:           ! Here's the real starting point
  1106. '
  1107. GOSUB restore_palette   ! We want to restore colors for multiple runs
  1108. '              otherwise print might be hard to read.
  1109. CLS
  1110. '
  1111. ' Do some more start up stuff.
  1112. '
  1113. PRINT AT(1,10);
  1114. INPUT "How many pixels/step (1 to 10)";stp$
  1115. IF stp$=""
  1116.  GOTO start
  1117. ENDIF
  1118. stp=VAL(stp$)
  1119. '
  1120. IF stp<1 OR stp>10  ! Check for valid range.
  1121.  GOTO start
  1122. ENDIF
  1123. '
  1124. minr=stp
  1125. CLS
  1126. FOR colour=1 TO 12
  1127.  DEFTEXT colour,17
  1128.  GOSUB title
  1129. NEXT colour
  1130. c=0
  1131.  
  1132.  
  1133.     The next few lines determine the starting point for the  first 
  1134. item to be drawn.
  1135.  
  1136.  
  1137. x=INT(RND(1)*320)
  1138. x1=x
  1139. y=INT(RND(1)*179)+20
  1140. y1=y
  1141. r=minr
  1142. dr=1
  1143. '
  1144. ' Main program loop follows:
  1145. '
  1146. REPEAT
  1147.  '
  1148.  GOSUB new_x
  1149.  GOSUB new_y
  1150.  '
  1151.  DEFFILL c
  1152.  INC c
  1153.  IF c>15
  1154.   c=1
  1155.  ENDIF
  1156.  IF dr=1
  1157.   INC r
  1158.  ENDIF
  1159.  IF dr=0
  1160.   DEC r
  1161.  ENDIF
  1162.  IF r=20
  1163.   dr=0
  1164.  ENDIF
  1165.  IF r=minr
  1166.   dr=1
  1167.  ENDIF
  1168.  '
  1169.  
  1170.  
  1171.  
  1172. Now determine which shape,  circle or square to draw; then display 
  1173. that shape on the screen.
  1174.  
  1175.  
  1176.  
  1177.  IF shape=0
  1178.   PCIRCLE x,y,r
  1179.  ELSE
  1180.   PBOX x,y,x+r,y+r
  1181.  ENDIF
  1182.  '
  1183.  GOSUB change_colour
  1184.  '
  1185.  k=MOUSEK
  1186. UNTIL k<>0
  1187. '
  1188. ' Left mouse button pressed?
  1189. '
  1190. IF k=1
  1191.  GOTO start
  1192. ENDIF
  1193. '
  1194. ' Right Mouse button pressed?
  1195. '
  1196. IF k=2 AND shape=0
  1197.  shape=1        ! Change shape to rectangle
  1198.  GOTO start
  1199. ENDIF
  1200. '
  1201. IF k=2 AND shape=1
  1202.  shape=0        ! Change shape to circle
  1203.  GOTO start
  1204. ENDIF
  1205. '
  1206. PAUSE 35        ! System needs a sec or 2 here.
  1207. CLS
  1208. GOSUB restore_palette
  1209. SHOWM
  1210. END
  1211. '
  1212.  
  1213.  
  1214.    Now we need to find a new value for x.
  1215.  
  1216.  
  1217. '
  1218. PROCEDURE new_x
  1219.  '
  1220.  IF x1>=319
  1221.   SUB x,stp
  1222.  ELSE
  1223.   ADD x,stp
  1224.  ENDIF
  1225.  ADD x1,stp
  1226.  IF x1>=643
  1227.   x1=stp
  1228.   x=stp
  1229.  ENDIF
  1230. RETURN
  1231. '
  1232.  
  1233.  
  1234.    Next we need a new y value.
  1235.  
  1236.  
  1237. '
  1238. PROCEDURE new_y
  1239.  '
  1240.  IF y1>199
  1241.   SUB y,stp
  1242.  ELSE
  1243.   ADD y,stp
  1244.  ENDIF
  1245.  ADD y1,stp
  1246.  IF y1>375
  1247.   y1=28
  1248.   y=28
  1249.  ENDIF
  1250. RETURN
  1251. '
  1252.  
  1253.  
  1254.    The following procedure is a useful routine you'll see often in 
  1255. this  book.  It saves the palette as set up by the user  from  the 
  1256. Control Panel, so that the default colors may be restored when the 
  1257. program ends.
  1258.  
  1259.  
  1260. ' Save Original Color Palette
  1261. '
  1262. PROCEDURE save_palette
  1263.  LOCAL i
  1264.  '
  1265.  FOR i=0 TO 15
  1266.   palette(i)=XBIOS(7,W:i,W:-1)
  1267.   pal(i)=palette(i)
  1268.  NEXT i
  1269.  '
  1270. RETURN
  1271. '
  1272. '
  1273.  
  1274.  
  1275.    Here's the procedure which restores the default color  palette. 
  1276. You'll see this one used again, too.
  1277.  
  1278.  
  1279. '
  1280. ' Restore Original Color Palette
  1281. '
  1282. PROCEDURE restore_palette
  1283.  LOCAL i
  1284.  '
  1285.  FOR i=0 TO 15
  1286.   SETCOLOR i,palette(i)
  1287.  NEXT i
  1288. RETURN
  1289. '
  1290.  
  1291.  
  1292.      To  give  the illusion of constant movement  on  the  screen, 
  1293. we're going to rotate the color palette. This procedure takes care 
  1294. of the rotation sequence.
  1295.  
  1296.  
  1297. PROCEDURE change_colour
  1298.  '
  1299.  temp=pal(1)
  1300.  FOR i=2 TO 15
  1301.   pal(i-1)=pal(i)
  1302.  NEXT i
  1303.  pal(15)=temp
  1304.  '
  1305.  FOR i=1 TO 15
  1306.   SETCOLOR i,pal(i)
  1307.  NEXT i
  1308.  FOR i=0 TO 15
  1309.   pal(i)=XBIOS(7,W:i,W:-1)
  1310.  NEXT i
  1311. RETURN
  1312. '
  1313.  
  1314.  
  1315.    Here is another routine to dazzle the beholder.  This procedure 
  1316. sets  up the title "Kaleidoscope" to alternate colors  with  color 
  1317. cycling.
  1318.  
  1319.  
  1320. PROCEDURE title
  1321.  IF colour=1
  1322.   TEXT 95,7,"K"
  1323.  ENDIF
  1324.  IF colour=2
  1325.   TEXT 105,7,"a"
  1326.  ENDIF
  1327.  IF colour=3
  1328.   TEXT 115,7,"l"
  1329.  ENDIF
  1330.  IF colour=4
  1331.   TEXT 125,7,"e"
  1332.  ENDIF
  1333.  IF colour=5
  1334.   TEXT 135,7,"i"
  1335.  ENDIF
  1336.  IF colour=6
  1337.   TEXT 145,7,"d"
  1338.  ENDIF
  1339.  IF colour=7
  1340.   TEXT 155,7,"o"
  1341.  ENDIF
  1342.  IF colour=8
  1343.   TEXT 165,7,"s"
  1344.  ENDIF
  1345.  IF colour=9
  1346.   TEXT 175,7,"c"
  1347.  ENDIF
  1348.  IF colour=10
  1349.   TEXT 185,7,"o"
  1350.  ENDIF
  1351.  IF colour=11
  1352.   TEXT 195,7,"p"
  1353.  ENDIF
  1354.  IF colour=12
  1355.   TEXT 205,7,"e"
  1356.  ENDIF
  1357. RETURN
  1358. '
  1359.  
  1360.  
  1361.     The set_color procedure is used to install our custom  palette 
  1362. when the program intializes.
  1363.  
  1364.  
  1365. PROCEDURE set_colour
  1366.  FOR i=0 TO 15
  1367.   dummy=XBIOS(7,pal2(i))
  1368.  NEXT i
  1369. RETURN
  1370.  
  1371.  
  1372.  
  1373. The Dragon Plot
  1374.  
  1375. Fractals  have  been  receiving  a  great  deal  of  attention  in 
  1376. mathematics  and  computer  graphics.   They're  being  used   for 
  1377. everything  from  simulating  random plant  growth  to  generating 
  1378. realistic planetary landscapes in science fiction films.
  1379.      Understanding fractals may not be as exciting as seeing  them 
  1380. in  action,  but  some explanation should prove  helpful  to  your 
  1381. programming.  The word fractal Çwas coined by Benoit Mandelbrot, a 
  1382. pioneer  in  their  study,  to denote curves  or  surfaces  having 
  1383. fractional  dimension.  The  idea of fractional dimension  can  be 
  1384. illustrated  as  a  straight curve (a line) which  has  only  one- 
  1385. dimension,  length.  If the curve is infinitely long and curves in 
  1386. such  a  manner  that it completely fills an  area  of  the  plane 
  1387. containing  it,  the curve can be  considered  two-dimensional.  A 
  1388. curve partially filling an area has a fractional dimension between 
  1389. 1 and 2.
  1390.     Many types of fractals are self-similar.  This means that  all 
  1391. portions of the fractal resemble each other.  This occurs whenever 
  1392. the  whole is an expansion of some basic building  block.  In  the 
  1393. language  of  fractals,  this basic building block is  called  the 
  1394. generator.
  1395.    The  generator  in the next program consists  of  a  number  of 
  1396. connected line segments.The curves plotted by this program are the 
  1397. result  of  starting  with  the  generator  and  then   repeatedly 
  1398. replacing  each line segment,  according to a  defined  rule.  The 
  1399. number of cycles is limited by the screen resolution.  Select  too 
  1400. high a number of cycles,  and the program will also slow down to a 
  1401. crawl.  Eventually,  the  screen  will be filled  by  the  fractal 
  1402. generator, as portions are plotted off the screen as well.
  1403.   This simple program which begins our exploration of the  world 
  1404. of  fractals plots a particular type of fractal  which  Mandelbrot 
  1405. labeled  a  "dragon  plot."  This  program  illustrates  a   self-
  1406. contacting curve.  A self-contacting curve touches,  but does  not 
  1407. cross,  itself.  The  generator consists of two-line  segments  of 
  1408. equal  length  forming  a right  angle.  During  each  cycle,  the 
  1409. generator is substituted for each segment on alternating sides  of 
  1410. the  segments.  (Even though GFA BASIC executes faster  than  most 
  1411. interpreted  languages,  it's still slow,  and that's part of  the 
  1412. fascination  of  the dragon plot --watching as your ST  plots  the 
  1413. figure, and noting the areas of similarity.
  1414.     DRAGON.BAS begins by asking you to enter an even  number  of 
  1415. cycles. When  a plot is complete,  pressing any key  clears  the 
  1416. screen  and returns you to the starting prompt.  Try starting  out 
  1417. with two cycles,  then four, then six, and so on.  As you add more 
  1418. cycles, more time is required to fill in the dragon.
  1419.  
  1420.  
  1421. Program 3-4. DRAGON.BAS
  1422.  
  1423.  
  1424. DIM sn(20)
  1425. in:
  1426. CLS
  1427. PRINT "Enter an even number of cycles (2-20)"
  1428. INPUT "or enter a zero to quit: ";nc$
  1429. nc=VAL(nc$)
  1430. IF nc=0
  1431.  END
  1432. ENDIF
  1433. IF nc<2 OR nc>20
  1434.  GOTO in
  1435. ENDIF
  1436. IF EVEN(nc)<>-1
  1437.  GOTO in
  1438. ENDIF
  1439. l=128
  1440. FOR c=2 TO nc STEP 2
  1441.  l=l/2
  1442. NEXT c
  1443. x=85
  1444. y=100
  1445. CLS
  1446. COLOR 3
  1447. PLOT x,y
  1448. FOR c=0 TO nc
  1449.  sn(c)=0
  1450. NEXT c
  1451. rot_seg:
  1452. d=0
  1453. FOR c=1 TO nc
  1454.  IF sn(c-1)=sn(c)
  1455.   d=d-1
  1456.   GOTO rotate_it
  1457.  ENDIF
  1458.  d=d+1
  1459.  rotate_it:
  1460.  IF d=-1
  1461.   d=7
  1462.  ENDIF
  1463.  IF d=8
  1464.   d=0
  1465.  ENDIF
  1466. NEXT c
  1467. IF d=0
  1468.  x=x+l+l
  1469.  GOTO seg
  1470. ENDIF
  1471. IF d=2
  1472.  y=y+l
  1473.  GOTO seg
  1474. ENDIF
  1475. IF d=4
  1476.  x=x-l-l
  1477.  GOTO seg
  1478. ENDIF
  1479. y=y-l
  1480. seg:
  1481. COLOR 3
  1482. DRAW TO x,y
  1483. sn(nc)=sn(nc)+1
  1484. FOR c=nc TO 1 STEP -1
  1485.  IF sn(c)<>2
  1486.   c=1
  1487.   GOTO next_seg
  1488.  ENDIF
  1489.  sn(c)=0
  1490.  sn(c-1)=sn(c-1)+1
  1491.  next_seg:
  1492. NEXT c
  1493. IF sn(0)=0
  1494.  GOTO rot_seg
  1495. ENDIF
  1496. PRINT AT(7,23);"Press any key to continue"
  1497. REPEAT
  1498. UNTIL INKEY$<>""
  1499. GOTO in
  1500.  
  1501.  
  1502.  
  1503. The Mandelbrot Set
  1504.  
  1505. You  can  see  fractals in nature  in  many  places.  The  clouds, 
  1506. coastlines  displayed in satellite photographs,  and even  a  leaf 
  1507. will  reveal fractals.  We've seen one form of  computer-generated 
  1508. fractals in Program 3-5,  the dragon sweep.  Now we'll explore one 
  1509. of the strangest and most beautiful areas of fractal geometry, the 
  1510. Mandelbrot set.
  1511.    The Mandelbrot set consists of complex numbers,  numbers with a 
  1512. "real" and "imaginary" part. These terms, real and imaginary, have 
  1513. historical  significance  in  mathematics,   but  are  no   longer 
  1514. relevant. A complex number takes the form of 6 + 3i; 6 is the real 
  1515. part  of the number,  and 3i represents the imaginary part  (hence 
  1516. the i).  Each complex number can be represented by a point on  the 
  1517. two-dimensional plane.
  1518.     The  Mandelbrot  set  is  located at  the  center  of  a  two-
  1519. dimensional  sheet  of numbers called the complex  plane.  When  a 
  1520. specific  operation  is applied repeatedly  to  the  numbers,  the 
  1521. numbers outside the set retreat to infinity. The remaining numbers 
  1522. move about within the plane. Near the edge of the set, the numbers 
  1523. move  about in a pattern which marks the beginning of the area  of 
  1524. instability.   This  area  is  astonishingly  beautiful,  complex, 
  1525. infinitely variable, and yet somehow, strangely similiar.
  1526.    The unique factor in numbers within the Mandelbrot set is  that 
  1527. values  in  the set never grow larger than 2 as  the  mathematical 
  1528. operation is performed on them.  Points within the Mandelbrot  set 
  1529. are represented in our program by black pixels.  The colors of the 
  1530. other  points are determined by counting the number of times  each 
  1531. complex  number is operated on before its value  exceeds  2.  This 
  1532. count is converted into a color.
  1533.    For more information on the theory of fractals, see The Fractal 
  1534. Geometry of Nature, by Benoit Mandelbrot.
  1535.  
  1536.  
  1537. Figure 3-8. The Mandelbrot Primitive
  1538.  
  1539.   Figure 3-8 shows a representation of the entire Mandelbrot  set. 
  1540. You  can  reproduce this figure  by  running  MANDELBROT.BAS,  and 
  1541. selecting 100 iterations, an X Center of .75, and a Y Center of 0. 
  1542. Choose  a range of 2 for viewing the complete image.  Once  you've 
  1543. become  somewhat  familiar  with the general  coordinates  of  the 
  1544. Mandelbrot set, try exploring the boundary area by selecting x and 
  1545. y coordinates located on the boundary,  and then selecting smaller 
  1546. values for the range.    Program 3-5,  MANDELBROT.BAS, was used to 
  1547. generate the image displayed in Figures 3-8, 3-9, and 3-10. Only a 
  1548. black-and-white representation was possible in the book,  but  the 
  1549. set  generated  by Program 3-5 is quite  colorful.     Some  other 
  1550. interesting areas to explore follow.
  1551.  
  1552. Figure 3-9. Mandelbrot Figure
  1553.  
  1554. Figure 3-10. Another Segment of the Mandelbrot Boundary.
  1555.  
  1556.  
  1557.  
  1558. X-Center   Y-Center    Range
  1559.   -1       0.32        0.3
  1560.   -1       0.2895      0.0005
  1561.   -0.97    0.276       0.0001
  1562.  
  1563.  
  1564.  
  1565.      In this program,  we'll be introducing several new procedures 
  1566. which can be used in your own programs.  We'll show you later  how 
  1567. to merge these procedures into your programs.
  1568.  
  1569.  
  1570. Program 3-5. MANDELBROT.BAS
  1571.  
  1572.  
  1573. DIM palette(15),pal2(15)
  1574.  
  1575.    The mouse pointer will be in the way on the picture,  so  we'll 
  1576. just turn it off.
  1577.  
  1578.  
  1579. '
  1580. HIDEM
  1581. '
  1582.  
  1583.  
  1584.     We'll  check to see which resolution is in use,  then  give  a 
  1585. warning if the machine isn't in low resolution.  This program will 
  1586. work  in any resolution;  it just looks best with  16  colors,  so 
  1587. we'll allow it to continue if the user doesn't want to quit.
  1588.  
  1589.  
  1590. '
  1591. rez=XBIOS(4)
  1592. IF rez<>0
  1593.  alrt$="Fractals look best in|Low Resolution"
  1594.  ALERT 1,alrt$,1,"Continue|Quit",b
  1595.  IF b=2
  1596.   END
  1597.  ENDIF
  1598. ENDIF
  1599. '
  1600.  
  1601.  
  1602.     Next  we'll  establish default  values  for  different  screen 
  1603. resolutions.
  1604.  
  1605.  
  1606.  
  1607. IF rez=0
  1608.  screen_height=200      ! Low res screen 
  1609.  screen_width=320       
  1610. ENDIF
  1611. '
  1612. IF rez=1            ! Medium resolution screen
  1613.  screen_height=200
  1614.  screen_width=640
  1615. ENDIF
  1616. '
  1617. IF rez=2            ! High resolution screen
  1618.  screen_height=400
  1619.  screen_width=640
  1620. ENDIF
  1621. '
  1622. ' Main Loop begins here
  1623. '
  1624.  
  1625.  
  1626.    We've used this routine before. It saves the palette so you can 
  1627. restore  the  original  colors  later.  It's  a  good  programming 
  1628. practice  to clean up after yourself.  If you change the  palette, 
  1629. then exit to the GFA BASIC editor,  you may find yourself stuck on 
  1630. a screen that is impossible to read.
  1631.  
  1632.  
  1633. GOSUB save_palette
  1634. '
  1635.  
  1636.  
  1637.    Here's the main loop which controls the program.
  1638.  
  1639.  
  1640. DO
  1641.  '
  1642.  GOSUB values
  1643.  IF rez=0
  1644.   GOSUB set_new_colors
  1645.  ENDIF
  1646.  GOSUB calculate
  1647.  IF rez=0
  1648.   GOSUB restore_palette
  1649.  ENDIF
  1650.  GOSUB display_it
  1651.  '
  1652. LOOP
  1653.  
  1654.  
  1655.     We'll put an END in here,  but the program never really  exits 
  1656. from the DO...LOOP.  Other procedures are called and executed from 
  1657. procedures  called by the DO...LOOP,  but everything  within  this 
  1658. program actually occurs within this loop.
  1659.  
  1660.  
  1661. '
  1662. END
  1663. '
  1664.  
  1665.  
  1666.    display_it is a procedure which displays information about  the 
  1667. calculations for this particular portion of the Mandelbrot set and 
  1668. offers  some  options  which may be selected by  pressing  a  key. 
  1669. Usually this procedure will be encountered after the  calculations 
  1670. for displaying the fractal are complete.
  1671.  
  1672. PROCEDURE display_it
  1673.  '
  1674.  display:
  1675.  CLS
  1676.  PRINT AT(1,3);"Fractal Image"
  1677.  PRINT AT(1,5);count;" Iterations Calculated."
  1678.  seconds=INT((time_finish-time_start)/2)/100
  1679.  min=INT(seconds/60)
  1680.  IF min<=0
  1681.   min=0
  1682.  ENDIF
  1683.  seconds=ABS(INT((seconds MOD 60)*100)/100)
  1684.  PRINT AT(1,7);min;" Minutes and ";seconds;" Seconds required."
  1685.  PRINT AT(1,8);"Number of iterations: ";iteration_limit
  1686.  PRINT AT(1,10);"X Center: ";x_center
  1687.  PRINT AT(1,11);"Y Center: ";y_center
  1688.  PRINT AT(1,12);"Scaling factor: ";range
  1689.  PRINT AT(1,14);"Minimum real value (xmin): ";real_min
  1690.  PRINT AT(1,15);"Maximum real value (xmax): ";real_max
  1691.  PRINT AT(1,16);"Minimum imaginary value (ymin): ";imag_min
  1692.  PRINT AT(1,17);"Maximum Imaginary value (ymax): ";imag_max
  1693.  PRINT AT(1,19);"Press:"
  1694.  PRINT AT(5,20);"<V> to View Fractal"
  1695.  PRINT AT(5,21);"<P> to Plot new Fractal"
  1696.  PRINT AT(5,22);"<S> to Save .NEO file"
  1697.  PRINT AT(5,23);"<Q> to Quit"
  1698.  '
  1699.  
  1700.  
  1701.     key waits for the user to press a key.  Then the key value  is 
  1702. stored in a$, and evaluated, and the proper branch is taken. UPPER 
  1703. is  a  GFA  BASIC  command  which converts  any  value  in  a$  to 
  1704. uppercase.  For  more  information about any GFA  BASIC  commands, 
  1705. refer to Chapter 2.
  1706.  
  1707.  
  1708.  key:
  1709.  REPEAT
  1710.   a$=INKEY$
  1711.  UNTIL a$<>""
  1712.  '
  1713.  IF UPPER$(a$)="V"
  1714.   SGET screen2$
  1715.   IF rez=0
  1716.    GOSUB set_new_colors
  1717.   ENDIF
  1718.   SPUT screen1$
  1719.   REPEAT
  1720.   UNTIL INKEY$<>""
  1721.   GOSUB restore_palette
  1722.   SPUT screen2$
  1723.  ENDIF
  1724.  '
  1725.  IF UPPER$(a$)="P"
  1726.   GOTO finito
  1727.  ENDIF
  1728.  '
  1729.  IF UPPER$(a$)="Q"
  1730.   SHOWM
  1731.   CLS
  1732.   END
  1733.  ENDIF
  1734.  '
  1735.  IF UPPER$(a$)="S"
  1736.   '
  1737.  
  1738.  
  1739.     Here's  a  handy  procedure  that  saves  the  screen  into  a 
  1740. NEOchrome-compatible file.  Following this program, we'll give you 
  1741. a simple routine which can be merged with your programs,  and show 
  1742. you  how  you  can use this routine to load screens  in  your  own 
  1743. programs. 
  1744.  
  1745.   IF rez<>0
  1746.    CLS
  1747.    ALRT$="Must be Low Res|for Neochrome files"
  1748.    ALERT 1,alrt$,1,"OKAY",b
  1749.   ENDIF
  1750.   GOTO not_neo
  1751.   '
  1752.   SGET screen2$
  1753.   default$="C:\*.NEO"
  1754.   FILESELECT default$,"",infile$
  1755.   CLS
  1756.   IF infile$=""           !equals "" if CANCEL selected
  1757.    GOTO not_neo
  1758.   ENDIF
  1759.   GOSUB set_new_colors
  1760.   SPUT screen1$
  1761.   OPEN "o",#1,infile$
  1762.   '
  1763.   ' First two bytes to zero
  1764.   '
  1765.   FOR i=0 TO 2
  1766.    OUT #1,0
  1767.    OUT #1,0
  1768.   NEXT i
  1769.   '
  1770.   ' Save color palette
  1771.   '
  1772.   FOR i=0 TO 15
  1773.    hi=INT(pal2(i)/256)
  1774.    lo=pal2(i)-256*hi
  1775.    OUT #1,hi
  1776.    OUT #1,lo
  1777.   NEXT i
  1778.   '
  1779.   ' Color cycling info (not needed)
  1780.   '
  1781.   FOR i=0 TO 89
  1782.    OUT #1,0
  1783.   NEXT i
  1784.   '
  1785.   ' Save screen info
  1786.   '
  1787.   BPUT #1,XBIOS(3),32000
  1788.   '
  1789.   CLOSE
  1790.   SPUT screen2$
  1791.   GOSUB restore_palette
  1792.   '
  1793.   not_neo:
  1794.   '
  1795.  ENDIF
  1796.  '
  1797.  GOTO display
  1798.  '
  1799.  finito:
  1800.  RETURN
  1801. '
  1802.  
  1803.  
  1804.     values  accepts  input  from the user for  the  values  to  be 
  1805. examined for the Mandelbrot boundaries.
  1806.  
  1807.  
  1808. PROCEDURE values
  1809.  '
  1810.  CLS
  1811.  INPUT "Number of iterations";iteration_limit
  1812.  INPUT "Center X";x_center
  1813.  INPUT "Center Y";y_center
  1814.  INPUT "Scale Range";range
  1815.  real_min=x_center-(range/2)
  1816.  real_max=x_center+(range/2)
  1817.  imag_max=y_center+((range/2)*0.77)
  1818.  imag_min=y_center-((range/2)*0.77)
  1819.  CLS
  1820. RETURN
  1821. '
  1822.     The next procedure does the real work.  The complex number  is 
  1823. evaluated  as defined.  Several arbitary values were selected  for 
  1824. constants.  You may find it interesting to change values,  such as 
  1825. max_limit,   to  observe  any  changes  in  the  figure   plotted. 
  1826. time_start  is used to calculate the time it took to complete  the 
  1827. plot.
  1828.     Note  that even though GFA BASIC is one  of  the  fastest 
  1829. interpreters available,  fractals can take a lot of time to  plot. 
  1830. Most  designs will take over an hour to complete.  The closer  the 
  1831. complex numbers are to the Mandelbrot set,  the more  calculations 
  1832. are required before the result exceeds 2.  Therefore, more time is 
  1833. required.
  1834.  
  1835.  
  1836. PROCEDURE calculate
  1837.  '
  1838.  time_start=INT(TIMER)
  1839.  max_limit=100000000
  1840.  count=0
  1841.  real=(real_max-real_min)/(screen_width-1)
  1842.  imaginary=(imag_max-imag_min)/(screen_height-1)
  1843.  FOR y=0 TO screen_height
  1844.   FOR x=0 TO screen_width
  1845.    lreal=real_min+x*real
  1846.    limag=imag_min+y*imaginary
  1847.    re=lreal
  1848.    im=limag
  1849.    depth=0
  1850.    calc_loop:
  1851.    INC count
  1852.    x1=re^2
  1853.    y1=im^2
  1854.    im=2*re*im-limag
  1855.    re=x1-y1-lreal
  1856.    INC depth
  1857.    IF ((depth=iteration_limit) OR ((x1+y1)>max_limit))
  1858.     GOTO finished_yet
  1859.    ELSE
  1860.     GOTO calc_loop
  1861.    ENDIF
  1862.    finished_yet:
  1863.    IF (depth<iteration_limit)
  1864.     GOSUB draw_point
  1865.    ENDIF
  1866.  
  1867.  
  1868.     Since we can get stuck here waiting on the calculations for  a 
  1869. long time, this will offer a way out and allow us a means to check 
  1870. on  the time spent and calculations completed on  this  particular 
  1871. set of complex numbers.
  1872.  
  1873.  
  1874.    IF INKEY$<>""
  1875.     GOSUB break
  1876.    ENDIF
  1877.   NEXT x
  1878.  NEXT y
  1879.  '
  1880.  ' Save screen into screen1$
  1881.  '
  1882.  SGET screen1$
  1883.  '
  1884.  time_finish=INT(TIMER)     ! time of completion
  1885.  '
  1886. RETURN
  1887. '
  1888.  
  1889.  
  1890.    If a key is pressed,  we must stop to evaluate it. We'll also 
  1891. display an interim screen with some interesting information. 
  1892.  
  1893. PROCEDURE break
  1894.  '
  1895.  SGET screen1$
  1896.  time_finish=INT(TIMER)
  1897.  IF rez=0
  1898.   GOSUB restore_palette
  1899.  ENDIF
  1900.  CLS
  1901.  PRINT AT(1,3);"Fractal Image"
  1902.  PRINT AT(1,5);count;" Iterations Calculated."
  1903.  seconds=INT((time_finish-time_start)/2)/100
  1904.  min=INT(seconds/60)
  1905.  IF min<=0
  1906.   min=0
  1907.  ENDIF
  1908.  seconds=ABS(INT((seconds MOD 60)*100)/100)
  1909.  PRINT AT(1,7);min;" Minutes and ";seconds;" Seconds required."
  1910.  PRINT AT(1,8);"Number of iterations: ";iteration_limit
  1911.  PRINT AT(1,10);"X Center: ";x_center
  1912.  PRINT AT(1,11);"Y Center: ";y_center
  1913.  PRINT AT(1,12);"Scaling factor: ";range
  1914.  PRINT AT(1,14);"Minimum real value (xmin): ";real_min
  1915.  PRINT AT(1,15);"Maximum real value (xmax): ";real_max
  1916.  PRINT AT(1,16);"Minimum imaginary value (ymin): ";imag_min
  1917.  PRINT AT(1,17);"Maximum Imaginary value (ymax): ";imag_max
  1918.  PRINT AT(1,19);"Press:"
  1919.  PRINT AT(5,20);"<C> to Continue Plot"
  1920.  PRINT AT(5,21);"<E> to Return to Main Menu"
  1921.  '
  1922.  keyit:
  1923.  REPEAT
  1924.   a$=INKEY$
  1925.  UNTIL a$<>""
  1926.  '
  1927.  IF UPPER$(a$)="E"
  1928.   x=screen_width
  1929.   y=screen_height
  1930.   SPUT screen1$
  1931.   GOTO finit
  1932.  ENDIF
  1933.  '
  1934.  IF UPPER$(a$)="C"
  1935.   IF rez=0
  1936.    GOSUB set_new_colors
  1937.   ENDIF
  1938.   SPUT screen1$
  1939.   GOTO finit
  1940.  ENDIF
  1941.  '
  1942.  GOTO keyit
  1943.  '
  1944.  finit:
  1945. RETURN
  1946.  
  1947.     The  calculations are completed;  now it's time  to  plot  the 
  1948. point.  Depth  is equal to the number of iterations calculated  on 
  1949. the number which represents t
  1950.  
  1951. he point. 
  1952.  
  1953. '
  1954. PROCEDURE draw_point
  1955.  '
  1956.  colour=depth MOD 16
  1957.  COLOR colour
  1958.  IF (depth>100)
  1959.   PLOT x,y
  1960.  ELSE
  1961.   GOSUB greater_than_two
  1962.  ENDIF
  1963. RETURN
  1964. '
  1965. PROCEDURE greater_than_two
  1966.  '
  1967.  IF depth MOD 2
  1968.   PLOT x,y
  1969.  ENDIF
  1970. RETURN
  1971. '
  1972.  
  1973.  
  1974.     set_new_colors  changes the color palette  by  installing  the 
  1975. colors we've selected into the hardware register for the palette.
  1976.  
  1977.  
  1978. PROCEDURE set_new_colors
  1979.  '
  1980.  ' Set up color table
  1981.  '
  1982.  pal2(0)=&H0
  1983.  pal2(1)=&H75
  1984.  pal2(2)=&H765
  1985.  pal2(3)=&H401
  1986.  pal2(4)=&H410
  1987.  pal2(5)=&H530
  1988.  pal2(6)=&H241
  1989.  pal2(7)=&H62
  1990.  pal2(8)=&H474
  1991.  pal2(9)=&H744
  1992.  pal2(10)=&H731
  1993.  pal2(11)=&H165
  1994.  pal2(12)=&H14
  1995.  pal2(13)=&H750
  1996.  pal2(14)=&H423
  1997.  pal2(15)=&H601
  1998.  '
  1999.  '
  2000.  FOR i=0 TO 15
  2001.   SETCOLOR i,pal2(i)
  2002.  NEXT i
  2003. RETURN
  2004. '
  2005.  
  2006.  
  2007.    We've seen the next two procedures before.
  2008.  
  2009. '
  2010. ' Save Original Color Palette
  2011. '
  2012. PROCEDURE save_palette
  2013.  LOCAL i
  2014.  '
  2015.  '
  2016.  FOR i=0 TO 15
  2017.   palette(i)=XBIOS(7,W:i,W:-1)
  2018.  NEXT i
  2019. RETURN
  2020. '
  2021. '
  2022. '
  2023. ' Restore Original Color Palette
  2024. '
  2025. PROCEDURE restore_palette
  2026.  LOCAL i
  2027.  '
  2028.  FOR i=0 TO 15
  2029.   SETCOLOR i,palette(i)
  2030.  NEXT i
  2031. RETURN
  2032.  
  2033.  
  2034.  
  2035.  
  2036.  
  2037.  
  2038. Saving a Screen in NEOchrome Format
  2039.  
  2040. Here's  a  simple  little  routine similar  to  the  one  used  in 
  2041. MANDELBROT.BAS. This program can easily be merged with any of your 
  2042. programs.
  2043.  
  2044. Program 3-6. NEOWRITE.BAS
  2045.  
  2046. Procedure Save_neoscreen
  2047. 'Reserve an area of memory for the alternate palette.
  2048.  
  2049.  '
  2050.  Dim Pal2(15)
  2051.  '
  2052.  Gosub Save_palette
  2053.  Hidem
  2054.  '
  2055.  Sget Screen1$
  2056.  '
  2057.  Rez=Xbios(4)
  2058.  If Rez<>0
  2059.   Cls
  2060.   Print ''Must be Low Resolution for Neochrome''
  2061.   Repeat
  2062.   Until Inkey$<>''''
  2063.   Cls
  2064.   Sput Screen1$
  2065.   Goto Not_neo
  2066.  Endif
  2067.  '
  2068.  Default$=''A:\*.NEO''
  2069.  Fileselect Default$,'''',Infile$
  2070.  Cls
  2071.  Sput Screen1$
  2072.  Open ''o'',#1,Infile$
  2073.  '
  2074.  ' First three words to zero
  2075.  '
  2076.  For I=0 To 2
  2077.   Out #1,0
  2078.   Out #1,0
  2079.  Next I
  2080.  '
  2081.  ' Save color palette
  2082.  '
  2083.  For I=0 To 15
  2084.   Hi=Int(Pal2(I)/256)
  2085.   Lo=Pal2(I)-256*Hi
  2086.   Out #1,Hi
  2087.   Out #1,Lo
  2088.  Next I
  2089.  '
  2090.  ' Color cycling info (not needed)
  2091.  '
  2092.  For I=0 To 89
  2093.   Out #1,0
  2094.  Next I
  2095.  '
  2096.  ' Save screen info
  2097.  '
  2098.  Bput #1,Xbios(3),32000
  2099.  '
  2100.  Close
  2101.  '
  2102.  Not_neo:
  2103.  '
  2104. Endif
  2105. '
  2106. '
  2107. Finito:
  2108. '
  2109. Return
  2110. '
  2111. ' Save Original Color Palette
  2112. '
  2113. Procedure Save_palette
  2114. Local I
  2115. '
  2116. '
  2117. '
  2118. For I=0 To 15
  2119.  Pal2(I)=Xbios(7,W:I,W:-1)
  2120. Next I
  2121. Return
  2122. '
  2123.  
  2124.  
  2125. After you've saved a screen in a NEOchrome format,  you'll need  a 
  2126. routine  to  display  the screen  without  loading  NEOCHROME.PRG. 
  2127. Here's a routine to load any NEOchrome-format screen. With a minor 
  2128. alteration,  you  may load any screen into your  programs  without 
  2129. using the fileselector box.
  2130.  
  2131. Program 3-7. NEOLOAD.BAS
  2132.  
  2133.  
  2134.  
  2135. DIM palette(15),pal2(15)
  2136. '
  2137. GOSUB save_palette
  2138. '
  2139.  
  2140.  
  2141. Here's the main loop.  Use these procedures as applicable in  your 
  2142. program  to load .NEO files.  Refer to the user's guide for  DEGAS 
  2143. Elite for information on how to handle a DEGAS file.  It's just as 
  2144. simple.
  2145.  
  2146.  
  2147. main:
  2148. '
  2149. GOSUB check_rez
  2150. GOSUB choose_pic
  2151. HIDEM
  2152. GOSUB load_colour
  2153. GOSUB install_colour
  2154. GOSUB show_pic
  2155. '
  2156. g$=''''
  2157. REPEAT
  2158.  g$=INKEY$
  2159. UNTIL g$<>''''
  2160. '
  2161. CLS
  2162. '
  2163. GOSUB restore_palette
  2164. '
  2165. IF UPPER$(g$)=''Q''
  2166.  END
  2167. ENDIF
  2168. '
  2169. SHOWM
  2170. GOTO main
  2171. '
  2172. '
  2173. PROCEDURE check_rez
  2174.  '
  2175.  rez=XBIOS(4)
  2176.  IF rez<>0
  2177.   alrt$=''NEOLOAD only works in|Low Resolution.''
  2178.   ALERT 3,alrt$,1,''Exit'',b
  2179.   END
  2180.  ENDIF
  2181.  '
  2182. RETURN
  2183. '
  2184. PROCEDURE choose_pic
  2185.  '
  2186.  
  2187.  
  2188. The next section was included to allow you to select a  NEOchrome-
  2189. format file using the standard GEM file selector. If you'd like to 
  2190. load  a  predetermined  file,   omit  this  procedure  and  define 
  2191. Filename$  as  the  name of the  desired  program  before  calling 
  2192. Procedure Load_colour.
  2193.  
  2194.  
  2195.  '
  2196.  disk$=''*.NEO''
  2197.  FILESELECT disk$,'''',filename$
  2198.  IF filename$=''''
  2199.   END
  2200.  ENDIF
  2201.  '
  2202. RETURN
  2203. '
  2204. PROCEDURE load_colour
  2205.  '
  2206.  OPEN ''I'',#1,filename$
  2207.  temp$=INPUT$(38,#1)
  2208.  
  2209.  
  2210.  
  2211. The first six bytes of the file don't matter,  so we'll strip them 
  2212. off.
  2213.  
  2214.  
  2215.  colour$=MID$(temp$,7,32)
  2216.  CLOSE #1
  2217.  '
  2218.  
  2219.  
  2220. Next, we'll break down the two-byte color values into values which 
  2221. we can assign to our alternate palette, and install the colors.
  2222.  
  2223.  
  2224.  palnum=0
  2225.  count=0
  2226.  REPEAT
  2227.   hibyte=ASC(MID$(colour$,count,1))
  2228.   INC count
  2229.   lobyte=ASC(MID$(colour$,count,1))
  2230.   INC count
  2231.   pal2(palnum)=(hibyte*256)+lobyte
  2232.   INC palnum
  2233.  UNTIL palnum=15
  2234.  '
  2235. RETURN
  2236. '
  2237.  
  2238. The  following XBIOS routine changes the hardware pointer  to  the 
  2239. palette  to point to the variable Colour$.  Changing this  pointer 
  2240. installs the new palette.
  2241.  
  2242.  
  2243.  
  2244. PROCEDURE install_colour
  2245.  '
  2246.  VOID XBIOS(6,L:VARPTR(colour$))
  2247.  '
  2248. RETURN
  2249. '
  2250.  
  2251.  
  2252.   Here's a little trick for loading the picture.  XBIOS (2) is  an 
  2253. XBIOS function which returns the location of the physical  screen. 
  2254. This will vary for 520s and 1040s.  Actually, we're cheating a bit 
  2255. here. We know that the first 128 bytes of a NEOchrome file contain 
  2256. information  we're not interested in (information  concerning  the 
  2257. resolution,  which is never used, the color palette, and the color 
  2258. rotation  ).  What we'll do is ignore this information  and  begin 
  2259. loading  the  picture into an absolute memory location  128  bytes 
  2260. lower than the beginning of screen memory. This area isn't usually 
  2261. used  for  anything,  and provides an easy way to  strip  off  the 
  2262. unneeded bytes and load the picture image.
  2263.  
  2264.  
  2265. PROCEDURE show_pic
  2266.  '
  2267.  physbase=XBIOS(2)
  2268.  BLOAD filename$,physbase-128
  2269.  '
  2270. RETURN
  2271. '
  2272. ' Save Original Color Palette
  2273. '
  2274. PROCEDURE save_palette
  2275.  '
  2276.  FOR i=0 TO 15
  2277.   palette(i)=XBIOS(7,W:i,W:-1)
  2278.  NEXT i
  2279.  '
  2280. RETURN
  2281. '
  2282. PROCEDURE restore_palette
  2283.  '
  2284.  FOR i=0 TO 15
  2285.   SETCOLOR i,palette(i)
  2286.  NEXT i
  2287.  '
  2288. RETURN
  2289.  
  2290.  
  2291.  
  2292. Great Graphics
  2293.  
  2294. As  you  have seen from these simple  examples,  GFA  BASIC  makes 
  2295. graphics programming easy.  It's not necessary to resort to PEEK's 
  2296. and POKE's to achieve the spectacular.  This is only the  starting 
  2297. point.  As you continue to explore graphics with GFA BASIC, you'll 
  2298. be  amazed  at the power you can unleash as use the power  of  the 
  2299. 68000 Microprocessor.
  2300.     In  the  next chapter,  we'll introduce you to  an  even  more 
  2301. impressive  use of graphics -- Animation.  Soon you'll be  writing 
  2302. the games you dream about.
  2303.